package br.com.games.pyx.mosaico;

import javax.microedition.khronos.opengles.GL10;
import javax.microedition.khronos.opengles.GL11;

import org.anddev.andengine.engine.camera.Camera;
import org.anddev.andengine.engine.handler.IUpdateHandler;
import org.anddev.andengine.entity.shape.RectangularShape;
import org.anddev.andengine.opengl.buffer.BufferObjectManager;
import org.anddev.andengine.opengl.util.GLHelper;
import org.anddev.andengine.opengl.vertex.RectangleVertexBuffer;

public class MosaicoAnimado extends RectangularShape {	
	
	private String nome;
	private ParteAnim mapa[][];
	private int compCelulas;
	private int altCelulas;
	
	private RectangleVertexBuffer mSharedVertexBuffer;	
	
	public MosaicoAnimado(String nome, int linhas, int colunas, int comprimentoCelulas, int alturaCelulas) {
		super(0, 0, 0, 0, null);
		this.nome = nome;
		mapa = new ParteAnim[linhas][colunas];
		
		compCelulas = comprimentoCelulas;
		altCelulas = alturaCelulas;
				
		this.mSharedVertexBuffer = new RectangleVertexBuffer(GL11.GL_STATIC_DRAW);
		BufferObjectManager.getActiveInstance().loadBufferObject(this.mSharedVertexBuffer);
		this.mSharedVertexBuffer.update(comprimentoCelulas, alturaCelulas);
		
		this.registerUpdateHandler(new UpdateHandler());
	}

	@Override
	@Deprecated
	public void setRotation(final float pRotation) {

	}	
	
	public void addCelula(ParteAnim part, int linha, int coluna) {
		mapa[linha][coluna] = part;
	}
	
	@Override
	protected void onInitDraw(final GL10 pGL) {
		super.onInitDraw(pGL);

		GLHelper.enableTextures(pGL);
		GLHelper.enableTexCoordArray(pGL);
	}	
	
	@Override
	protected void onApplyVertices(final GL10 pGL) {
		if(GLHelper.EXTENSIONS_VERTEXBUFFEROBJECTS) {
			final GL11 gl11 = (GL11)pGL;

			mSharedVertexBuffer.selectOnHardware(gl11);
			GLHelper.vertexZeroPointer(gl11);
		} else {
			GLHelper.vertexPointer(pGL, mSharedVertexBuffer.getFloatBuffer());
		}
	}	
	
	@Override
	protected void drawVertices(GL10 pGL, Camera pCamera) {

		int totalW = 0;				
		
		//TODO Otimizar exibindo apenas os tiles que estão visiveis
		
		for(int i = 0; i < mapa.length; i++) {//linha
			for(int j = 0; j < mapa[i].length; j++) {//coluna
				
				ParteAnim parte = mapa[i][j];
				try {
					if (parte != null) {
						parte.frames[parte.frame].onApply(pGL);
						pGL.glDrawArrays(GL10.GL_TRIANGLE_STRIP, 0, 4);
					}
				} catch(Throwable ex) {
					ex.printStackTrace();
				}
				
				totalW += compCelulas;
				pGL.glTranslatef(compCelulas, 0, 0);
			}
			
			pGL.glTranslatef(-totalW, altCelulas, 0);
			totalW = 0;
		}
		
		pGL.glLoadIdentity();
				
	}
	
	public String getNome() {
		return nome;
	}
	
	public void setNome(String nome) {
		this.nome = nome;
	}

	public int getCompCelulas() {
		return compCelulas;
	}

	public void setCompCelulas(int compCelulas) {
		this.compCelulas = compCelulas;
	}

	public int getAltCelulas() {
		return altCelulas;
	}

	public void setAltCelulas(int altCelulas) {
		this.altCelulas = altCelulas;
	}

	@Override
	protected void onUpdateVertexBuffer() {
		
	}

	class UpdateHandler implements IUpdateHandler {

		@Override
		public void onUpdate(float pSecondsElapsed) {
			for(int i = 0; i < mapa.length; i++) {//linha
				for(int j = 0; j < mapa[i].length; j++) {//coluna
					ParteAnim parte = mapa[i][j];
					
					if(parte != null)
						parte.update((long)(1000*pSecondsElapsed));
				}
				
			}				
		}

		@Override
		public void reset() {
			
		}
		
	}
	
}
